package com.yc.vote.util;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Map;

import javax.servlet.http.HttpServletRequest;

public class RequestParamUtil {

	/**
	 * 将请求中的参数转成对应的对象返回
	 * @param <T>
	 * @param request
	 * @param cls
	 * @return
	 */
	public static <T> T getParams(HttpServletRequest request, Class<T> cls){
		T t = null;
		
		try {
			t = cls.newInstance(); // 实例化一个这个类的对象
			Enumeration<String> names = request.getParameterNames(); // 获取请求中参数的名称
			
			//获取类中所有的setter方法
			Method[] methods = cls.getDeclaredMethods(); // 获取类中所有的方法
			Map<String, Method> setters = new HashMap<String, Method>();
			
			String methodName = null;
			for(Method method : methods) {
				methodName = method.getName();
				if(methodName.startsWith("set")) {
					setters.put(methodName, method);
				}
			}
			
			String name = null;
			Class<?>[] types = null;
			Class<?> type = null;
			Method method = null;
			String val = null;
			
			while(names.hasMoreElements()) { // 如果还有请求
				name = names.nextElement(); // 获取请求的参数名
				methodName = "set" + name.substring(0, 1).toUpperCase() + name.substring(1);
				
				method = setters.get(methodName); // 是否有处理这个参数的方法
				if(method == null) {
					continue;
				}
				
				types = method.getParameterTypes(); // 获取这个方法的形参类型列表
				if(types == null || types.length <= 0) {
					continue;
				}
				
				val = request.getParameter(name); // 获取这个参数的值
				type = types[0]; // 获取形参列表的第一个参数的类型
				if(Integer.TYPE == type) {
					method.invoke(t, Integer.parseInt(val));
					continue;
				}
				
				if(Integer.class == type) {
					method.invoke(t, Integer.valueOf(val));
					continue;
				}
				
				if(Long.TYPE == type) {
					method.invoke(t, Long.parseLong(val));
					continue;
				}
				
				if(Long.class == type) {
					method.invoke(t, Long.valueOf(val));
					continue;
				}
				
				if(Double.TYPE == type) {
					method.invoke(t, Double.parseDouble(val));
					continue;
				}
				
				if(Double.class == type) {
					method.invoke(t, Double.valueOf(val));
					continue;
				}
				
				method.invoke(t, val);
			}
		} catch (NumberFormatException e) {
			e.printStackTrace();
		} catch (InstantiationException e) {
			e.printStackTrace();
		} catch (IllegalAccessException e) {
			e.printStackTrace();
		} catch (SecurityException e) {
			e.printStackTrace();
		} catch (IllegalArgumentException e) {
			e.printStackTrace();
		} catch (InvocationTargetException e) {
			e.printStackTrace();
		}
		return t;
	}
	
}
